package com.rw.engine;

import org.springframework.web.servlet.HandlerExceptionResolver;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;


/**
 * 公共异常拦截器
 * 因为有许多验证器会直接抛出异常
 * 每种验证器都需要配置对应的异常拦截器
 * 由此写出此父类来提高代码复用
 * <p>
 * 由于Spring-Engine的低侵入性
 * 用户可以自己配置对应的异常拦截器
 * 所以这里只需要返回最常用的默认的json结果即可
 *
 * @param <T> 子类的异常类型
 */
public abstract class CommonExceptionResolver<T extends Exception> implements HandlerExceptionResolver {
    /**
     * 需要拦截的异常
     */
    private final Class<T> exceptionClass;

    /**
     * 构建异常拦截器
     *
     * @param exceptionClass 需要拦截的异常
     */
    protected CommonExceptionResolver(Class<T> exceptionClass) {
        this.exceptionClass = exceptionClass;
    }

    @Override
    public ModelAndView resolveException(HttpServletRequest request, HttpServletResponse response, Object handler,
                                         Exception ex) {
        // 如果异常不为目标异常，则直接返回
        if (ex.getClass() != exceptionClass) {
            return null;
        }

        // 获取异常对象
        T exception = exceptionClass.cast(ex);

        // 调用子类的方法，并返回对应的值
        return resolveTargetException(request, response, handler, exception);
    }

    /**
     * 根据对应的异常，返回对应的值
     *
     * @param request  HttpServletRequest对象
     * @param response HttpServletResponse对象
     * @param handler  处理器对象
     * @param ex       异常对象
     * @return 返回的ModelAndView
     */
    public abstract ModelAndView resolveTargetException(HttpServletRequest request, HttpServletResponse response,
                                                        Object handler,
                                                        T ex);
}
